home *** CD-ROM | disk | FTP | other *** search
- Chapter 5 - Functions and variables
-
-
- OUR FIRST USER DEFINED FUNCTION
-
- Load and examine the file SUMSQRES.C for an example of
- a C program with functions. Actually this is not the first
- function we have encountered because the "main" program we
- have been using all along is technically a function, as is
- the "printf" function. The "printf" function is a library
- function that was supplied with your compiler.
-
- Notice the executable part of this program. It begins
- with a line that simply says "header()", which is the way to
- call any function. The parentheses are required because the
- C compiler uses them to determine that it is a function call
- and not simply a misplaced variable. When the program comes
- to this line of code, the function named "header" is called,
- its statements are executed, and control returns to the
- statement following this call. Continuing on we come to a
- "for" loop which will be executed 7 times and which calls
- another function named "square" each time through the loop,
- and finally a function named "ending" will be called and
- executed. For the moment ignore the "index" in the
- parentheses of the call to "square". We have seen that this
- program therefore calls a header, 7 square calls, and an
- ending. Now we need to define the functions.
-
- DEFINING THE FUNCTIONS
-
- Following the main program you will see another program
- that follows all of the rules set forth so far for a "main"
- program except that it is named "header()". This is the
- function which is called from within the main program. Each
- of these statements are executed, and when they are all
- complete, control returns to the main program.
-
- The first statement sets the variable "sum" equal to
- zero because we will use it to accumulate a sum of squares.
- Since the variable "sum" is defined as an integer type
- variable prior to the main program, it is available to be
- used in any of the following functions. It is called a
- "global" variable, and it's scope is the entire program and
- all functions. More will be said about the scope of
- variables at the end of this chapter. The next statement
- outputs a header message to the monitor. Program control
- then returns to the main program since there are no
- additional statements to execute in this function.
-
- It should be clear to you that the two executable lines
- from this function could be moved to the main program,
- replacing the header call, and the program would do exactly
- the same thing that it does as it is now written. This does
- not minimize the value of functions, it merely illustrates
-
-
- Page 29
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- the operation of this simple function in a simple way. You
- will find functions to be very valuable in C programming.
-
- PASSING A VALUE TO A FUNCTION
-
- Going back to the main program, and the "for" loop
- specifically, we find the new construct from the end of the
- last lesson used in the last part of the for loop, namely
- the "index++". You should get used to seeing this, as you
- will see it a lot in C programs.
-
- In the call to the function "square", we have an added
- feature, namely the variable "index" within the parentheses.
- This is an indication to the compiler that when you go to
- the function, you wish to take along the value of index to
- use in the execution of that function. Looking ahead at the
- function "square", we find that another variable name is
- enclosed in its parentheses, namely the variable "number".
- This is the name we prefer to call the variable passed to
- the function when we are in the function. We can call it
- anything we wish as long as it follows the rules of naming
- an identifier. Since the function must know what type the
- variable is, it is defined following the function name but
- before the opening brace of the function itself. Thus, the
- line containing "int number;" tells the function that the
- value passed to it will be an integer type variable. With
- all of that out of the way, we now have the value of index
- from the main program passed to the function "square", but
- renamed "number", and available for use within the function.
-
- Following the opening brace of the function, we define
- another variable "numsq" for use only within the function
- itself, (more about that later) and proceed with the
- required calculations. We set "numsq" equal to the square
- of number, then add numsq to the current total stored in
- "sum". Remember that "sum += numsq" is the same as "sum =
- sum + numsq" from the last lesson. We print the number and
- its square, and return to the main program.
-
- MORE ABOUT PASSING A VALUE TO A FUNCTION
-
- When we passed the value of "index" to the function, a
- little more happened than meets the eye. We did not
- actually pass the value of index to the function, we
- actually passed a copy of the value. In this way the
- original value is protected from accidental corruption by a
- called function. We could have modified the variable
- "number" in any way we wished in the function "square", and
- when we returned to the main program, "index" would not have
- been modified. We thus protect the value of a variable in
- the main program from being accidentally corrupted, but we
-
-
- Page 30
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- cannot return a value to the main program from a function
- using this technique. We will find a well defined method of
- returning values to the main program or to any calling
- function when we get to arrays and another method when we
- get to pointers. Until then the only way you will be able
- to communicate back to the calling function will be with
- global variables. We have already hinted at global
- variables above, and will discuss them in detail later in
- this chapter.
-
- Continuing in the main program, we come to the last
- function call, the call to "ending". This call simply calls
- the last function which has no local variables defined. It
- prints out a message with the value of "sum" contained in it
- to end the program. The program ends by returning to the
- main program and finding nothing else to do. Compile and
- run this program and observe the output.
-
- NOW TO CONFESS A LITTLE LIE
-
- I told you a short time ago that the only way to get a
- value back to the main program was through use of a global
- variable, but there is another way which we will discuss
- after you load and display the file named SQUARES.C. In
- this file we will see that it is simple to return a single
- value from a called function to the calling function. But
- once again, it is true that to return more than one value,
- we will need to study either arrays or pointers.
-
- In the main program, we define two integers and begin a
- "for" loop which will be executed 8 times. The first
- statement of the for loop is "y = squ(x);", which is a new
- and rather strange looking construct. From past experience,
- we should have no trouble understanding that the "squ(x)"
- portion of the statement is a call to the "squ" function
- taking along the value of "x" as a variable. Looking ahead
- to the function itself we find that the function prefers to
- call the variable "in" and it proceeds to square the value
- of "in" and call the result "square". Finally, a new kind
- of a statement appears, the "return" statement. The value
- within the parentheses is assigned to the function itself
- and is returned as a usable value in the main program.
- Thus, the function call "squ(x)" is assigned the value of
- the square and returned to the main program such that "y" is
- then set equal to that value. If "x" were therefore
- assigned the value 4 prior to this call, "y" would then be
- set to 16 as a result of this line of code.
-
- Another way to think of this is to consider the
- grouping of characters "squ(x)" as another variable with a
- value that is the square of "x", and this new variable can
-
-
- Page 31
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- be used any place it is legal to use a variable of its type.
- The values of "x" and "y" are then printed out.
-
- To illustrate that the grouping of "squ(x)" can be
- thought of as just another variable, another "for" loop is
- introduced in which the function call is placed in the print
- statement rather than assigning it to a new variable.
-
- One last point must be made, the type of variable
- returned must be defined in order to make sense of the data,
- but the compiler will default the type to integer if none is
- specified. If any other type is desired, it must be
- explicitly defined. How to do this will be demonstrated in
- the next example program.
-
- Compile and run this program.
-
- FLOATING POINT FUNCTIONS
-
- Load the program FLOATSQ.C for an example of a function
- with a floating point type of return. It begins by defining
- a global floating point variable we will use later. Then in
- the "main" part of the program, an integer is defined,
- followed by two floating point variables, and then by two
- strange looking definitions. The expressions "sqr()" and
- "glsqr()" look like function calls and they are. This is
- the proper way in C to define that a function will return a
- value that is not of the type "int", but of some other type,
- in this case "float". This tells the compiler that when a
- value is returned from either of these two functions, it
- will be of type "float".
-
- Now refer to the function "sqr" near the center of the
- listing and you will see that the function name is preceded
- by the name "float". This is an indication to the compiler
- that this function will return a value of type "float" to
- any program that calls it. The function is now compatible
- with the call to it. The line following the function name
- contains "float inval;", which indicates to the compiler
- that the variable passed to this function from the calling
- program will be of type "float".
-
- The next function, namely "glsqr", will also return a
- "float" type variable, but it uses a global variable for
- input. It also does the squaring right within the return
- statement and therefore has no need to define a separate
- variable to store the product.
-
- The overall structure of this program should pose no
- problem and will not be discussed in any further detail. As
-
-
-
- Page 32
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- is customary with all example programs, compile and run this
- program.
-
- There will be times that you will have a need for a
- function to return a pointer as a result of some
- calculation. There is a way to define a function so that it
- does just that. We haven't studied pointers yet, but we
- will soon. This is just a short preview of things to come.
-
- SCOPE OF VARIABLES
-
- Load the next program, SCOPE.C, and display it for a
- discussion of the scope of variables in a program.
-
- The first variable defined is a global variable "count"
- which is available to any function in the program since it
- is defined before any of the functions. In addition, it is
- always available because it does not come and go as the
- program is executed. (That will make sense shortly.)
- Farther down in the program, another global variable named
- "counter" is defined which is also global but is not
- available to the main program since it is defined following
- the main program. A global variable is any variable that is
- defined outside of any function. Note that both of these
- variables are sometimes referred to as external variables
- because they are external to any functions.
-
- Return to the main program and you will see the
- variable "index" defined as an integer. Ignore the word
- "register" for the moment. This variable is only available
- within the main program because that is where it is defined.
- In addition, it is an "automatic" variable, which means that
- it only comes into existence when the function in which it
- is contained is invoked, and ceases to exist when the
- function is finished. This really means nothing here
- because the main program is always in operation, even when
- it gives control to another function. Another integer is
- defined within the "for" braces, namely "stuff". Any
- pairing of braces can contain a variable definition which
- will be valid and available only while the program is
- executing statements within those braces. The variable will
- be an "automatic" variable and will cease to exist when
- execution leaves the braces. This is convenient to use for
- a loop counter or some other very localized variable.
-
- MORE ON "AUTOMATIC" VARIABLES
-
- Observe the function named "head1". It contains a
- variable named "index", which has nothing to do with the
- "index" of the main program, except that both are automatic
- variables. When the program is not actually executing
-
-
- Page 33
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- statements in this function, this variable named "index"
- does not even exist. When "head1" is called, the variable
- is generated, and when "head1" completes its task, the
- variable "index" is eliminated completely from existence.
- Keep in mind however that this does not affect the variable
- of the same name in the main program, since it is a
- completely separate entity.
-
- Automatic variables therefore, are automatically
- generated and disposed of when needed. The important thing
- to remember is that from one call to a function to the next
- call, the value of an automatic variable is not preserved
- and must therefore be reinitialized.
-
- WHAT ARE STATIC VARIABLES?
-
- An additional variable type must be mentioned at this
- point, the "static" variable. By putting the reserved word
- "static" in front of a variable declaration within a
- function, the variable or variables in that declaration are
- static variables and will stay in existence from call to
- call of the particular function.
-
- By putting the same reserved word in front of an
- external variable, one outside of any function, it makes the
- variable private and not accessible to use in any other
- file. This implies that it is possible to refer to external
- variables in other separately compiled files, and that is
- true. Examples of this usage will be given in chapter 14 of
- this tutorial.
-
- USING THE SAME NAME AGAIN
-
- Refer to the function named "head2". It contains
- another definition of the variable named "count". Even
- though "count" has already been defined as a global
- variable, it is perfectly all right to reuse the name in
- this function. It is a completely new variable that has
- nothing to do with the global variable of the same name, and
- causes the global variable to be unavailable in this
- function. This allows you to write programs using existing
- functions without worrying about what names were used for
- variables in the functions because there can be no conflict.
- You only need to worry about the variables that interface
- with the functions.
-
- WHAT IS A REGISTER VARIABLE?
-
- Now to fulfill a promise made earlier about what a
- register variable is. A computer can keep data in a
- register or in memory. A register is much faster in
-
-
- Page 34
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- operation than memory but there are very few registers
- available for the programmer to use. If there are certain
- variables that are used extensively in a program, you can
- designate that those variables are to be stored in a
- register if possible in order to speed up the execution of
- the program. Depending on the computer and the compiler, a
- small number of register variables may be allowed and are
- designated by putting the word "register" in front of the
- desired variable. Check your compiler documentation for the
- availability of this feature and the number of register
- variables. Most compilers that do not have any register
- variables available, will simply ignore the word "register"
- and run normally, keeping all variables in memory.
-
- Register variables are only available for use with
- integer and character type variables. This may or may not
- include some of the other integer-like variables such as
- unsigned, long, or short. Check the documentation for your
- compiler.
-
- WHERE DO I DEFINE VARIABLES?
-
- Now for a refinement on a general rule stated earlier.
- When you have variables brought to a function as arguments
- to the function, they are defined immediately after the
- function name and prior to the opening brace for the
- program. Other variables used in the function are defined
- at the beginning of the function, immediately following the
- opening brace of the function, and before any executable
- statements.
-
- STANDARD FUNCTION LIBRARIES
-
- Every compiler comes with some standard predefined
- functions which are available for your use. These are
- mostly input/output functions, character and string
- manipulation functions, and math functions. We will cover
- most of these in subsequent chapters.
-
- In addition, most compilers have additional functions
- predefined that are not standard but allow the programmer to
- get the most out of his particular computer. In the case of
- the IBM-PC and compatibles, most of these functions allow
- the programmer to use the BIOS services available in the
- operating system, or to write directly to the video monitor
- or to any place in memory. These will not be covered in any
- detail as you will be able to study the unique aspects of
- your compiler on your own. Many of these kinds of functions
- are used in the example programs in chapter 14.
-
-
-
-
- Page 35
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- WHAT IS RECURSION?
-
- Recursion is another of those programming techniques
- that seem very intimidating the first time you come across
- it, but if you will load and display the example program
- named RECURSON.C, we will take all of the mystery out of it.
- This is probably the simplest recursive program that it is
- possible to write and it is therefore a stupid program in
- actual practice, but for purposes of illustration, it is
- excellent.
-
- Recursion is nothing more than a function that calls
- itself. It is therefore in a loop which must have a way of
- terminating. In the program on your monitor, the variable
- "index" is set to 8, and is used as the argument to the
- function "count_dn". The function simply decrements the
- variable, prints it out in a message, and if the variable is
- not zero, it calls itself, where it decrements it again,
- prints it, etc. etc. etc. Finally, the variable will reach
- zero, and the function will not call itself again. Instead,
- it will return to the prior time it called itself, and
- return again, until finally it will return to the main
- program and will return to DOS.
-
- For purposes of understanding you can think of it as
- having 8 copies of the function "count_dn" available and it
- simply called all of them one at a time, keeping track of
- which copy it was in at any given time. That is not what
- actually happened, but it is a reasonable illustration for
- you to begin understanding what it was really doing.
-
- WHAT DID IT DO?
-
- A better explanation of what actually happened is in
- order. When you called the function from itself, it stored
- all of the variables and all of the internal flags it needs
- to complete the function in a block somewhere. The next
- time it called itself, it did the same thing, creating and
- storing another block of everything it needed to complete
- that function call. It continued making these blocks and
- storing them away until it reached the last function when it
- started retrieving the blocks of data, and using them to
- complete each function call. The blocks were stored on an
- internal part of the computer called the "stack". This is a
- part of memory carefully organized to store data just as
- described above. It is beyond the scope of this tutorial to
- describe the stack in detail, but it would be good for your
- programming experience to read some material describing the
- stack. A stack is used in nearly all modern computers for
- internal housekeeping chores.
-
-
-
- Page 36
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- In using recursion, you may desire to write a program
- with indirect recursion as opposed to the direct recursion
- described above. Indirect recursion would be when a
- function "A" calls the function "B", which in turn calls
- "A", etc. This is entirely permissible, the system will
- take care of putting the necessary things on the stack and
- retrieving them when needed again. There is no reason why
- you could not have three functions calling each other in a
- circle, or four, or five, etc. The C compiler will take
- care of all of the details for you.
-
- The thing you must remember about recursion is that at
- some point, something must go to zero, or reach some
- predefined point to terminate the loop. If not, you will
- have an infinite loop, and the stack will fill up and
- overflow, giving you an error and stopping the program
- rather abruptly.
-
- ANOTHER EXAMPLE OF RECURSION
-
- The program named BACKWARD.C is another example of
- recursion, so load it and display it on your screen. This
- program is similar to the last one except that it uses a
- character array. Each successive call to the function named
- "forward_and_backward" causes one character of the message
- to be printed. Additionally, each time the function ends,
- one of the characters is printed again, this time backwards
- as the string of recursive function calls is retraced.
-
- Don't worry about the character array defined in line 3
- or the other new material presented here. After you
- complete chapter 7 of this tutorial, this program will make
- sense. It was felt that introducing a second example of
- recursion was important so this file is included here.
-
- One additional feature is built into this program. If
- you observe the two calls to the function, and the function
- itself, you will see that the function name is spelled three
- different ways in the last few characters. The compiler
- doesn't care how they are spelled because it only uses the
- first 8 characters of the function name so as far as it is
- concerned, the function is named "forward_". The remaining
- characters are simply ignored. If your compiler uses more
- that 8 characters as being significant, you will need to
- change two of the names so that all three names are
- identical.
-
- Compile and run this program and observe the results.
-
-
-
-
-
- Page 37
-
-
-
-
-
-
-
-
-
- Chapter 5 - Functions and variables
-
-
- PROGRAMMING EXERCISES
-
- 1. Rewrite TEMPCONV.C, from an earlier chapter, and move
- the temperature calculation to a function.
-
- 2. Write a program that writes your name on the monitor 10
- times by calling a function to do the writing. Move the
- called function ahead of the "main" function to see if
- your compiler will allow it.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- Page 38
-